package org.ym.file.domain.model.rule;

import lombok.*;
import org.apache.commons.lang3.StringUtils;
import org.ym.database.hibernate.base.BaseModel;
import org.ym.file.domain.model.rule.embed.FileRuleSystemNode;
import org.ym.file.domain.model.rule.embed.RuleDetail;
import org.ym.tools.adapter.IgnoreField;

import javax.persistence.*;
import java.util.*;

/**
 * 文件存储规则
 * @author ym
 */
@Entity
@Table(name = "f_rule")
@Getter(AccessLevel.PROTECTED)
@NoArgsConstructor(access = AccessLevel.PROTECTED)
@AllArgsConstructor(access = AccessLevel.PRIVATE)
@Builder
@EqualsAndHashCode(callSuper = true)
@ToString(callSuper = true)
public class FileRule extends BaseModel {
    private static final long serialVersionUID = 2798690491320989248L;
    /**
     * 规则名称
     */
    @Column(name = "name",length = 100,nullable = false)
    private String name;
    /**
     * 文件系统节点
     */
    @ElementCollection(targetClass = FileRuleSystemNode.class)
    @CollectionTable(name = "f_rule_system_node"
            ,uniqueConstraints = @UniqueConstraint(columnNames = {"rule_id","file_system_node_id"})
            ,joinColumns = {@JoinColumn(name = "rule_id",referencedColumnName = "id")}
    )
    List<FileRuleSystemNode> fileSystemNodeList = new ArrayList<>();
    /**
     * 规则
     */
    @ElementCollection(targetClass = RuleDetail.class)
    @CollectionTable(name = "f_rule_detail"
            ,joinColumns = {@JoinColumn(name = "rule_id",referencedColumnName = "id")}
    )
    Set<RuleDetail> ruleDetailSet = new HashSet<>();
    /**
     * 备注
     */
    @Column(name = "memo",length = 500)
    private String memo;

    /**
     * 文件节点索引
     */
    @Transient
    @IgnoreField
    private Integer fileSystemNodeIndex = 0;

    /**
     * 文件是否匹配当前规则要求
     * @param fileName 文件
     * @return true：匹配 / false：不匹配
     */
    public boolean isMatch(String fileName){
        boolean isMatch = false;
        if(StringUtils.isNotBlank(fileName) && !fileSystemNodeList.isEmpty()){
            for(RuleDetail ruleDetail : ruleDetailSet){
                if(ruleDetail.isMatch(fileName)){
                    isMatch = true;
                    break;
                }
            }
        }
        return isMatch;
    }

    /**
     * 获取匹配到的系统节点
     * @return 系统节点主键
     */
    public Long nextSystemNode(){
        int index;
        synchronized (this) {
            if (fileSystemNodeIndex >= fileSystemNodeList.size()) {
                fileSystemNodeIndex = 0;
            }
            index = fileSystemNodeIndex;
            fileSystemNodeIndex++;
        }
        return fileSystemNodeList.get(index).getFileSystemNodeId();
    }

    /**
     * 清空节点
     */
    public void clearSystemNode(){
        this.fileSystemNodeList = new ArrayList<>();
    }

    /**
     * 清空规则
     */
    public void clearRules(){
        this.ruleDetailSet = new HashSet<>();
    }
}
